package com.devops.admin.service.impl;

import cn.hutool.core.util.ObjectUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.devops.admin.mapper.DOSProjectGroupMapper;
import com.devops.admin.model.*;
import com.devops.admin.service.DOSProjectGroupService;
import com.devops.admin.service.DOSProjectService;
import com.devops.admin.util.Assert;
import com.devops.admin.vo.DOSPageVo;
import com.devops.shiro.vm.BaseUserVM;
import org.apache.shiro.SecurityUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.Comparator;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * @ClassNem DOSProjectGroupServiceImpl
 * @Description TODO
 * @Author heyabo
 * @Date 2022/3/21 16:01
 * @Version 1.0
 **/
@Service
public class DOSProjectGroupServiceImpl extends ServiceImpl<DOSProjectGroupMapper, DOSProjectGroup> implements DOSProjectGroupService {
    @Autowired
    private DOSProjectService dosProjectService;

    @Override
    public TableResult<DOSProjectGroup> getListPage(DOSModel modelPage, DOSPageVo pageVo) {
        Page<DOSProjectGroup> page = new Page<>(pageVo.getPageNum(),pageVo.getPageSize());
        TableResult<DOSProjectGroup> tableResult = new TableResult<>();
        LambdaQueryWrapper<DOSProjectGroup> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.orderByDesc(DOSProjectGroup::getCreateTime);
        Page<DOSProjectGroup> selectPage = baseMapper.selectPage(page, queryWrapper);
        Pagination p = Pagination.builder().pageNum(selectPage.getCurrent()).pageSize(selectPage.getSize()).total(selectPage.getTotal()).build();
        tableResult.setList(selectPage.getRecords());
        tableResult.setPagination(p);
        return tableResult;
    }

    @Override
    public Boolean deleteProjectGroup(Integer projectGroupId) {
        //首先判断项目组下面是否绑定项目
        Assert.isTrue( dosProjectService.count(Wrappers.<DOSProject>lambdaQuery().eq(DOSProject::getGroupId,projectGroupId)) == 0,"项目组绑定有项目不能删除");
        return this.removeById(projectGroupId);
    }

    @Override
    public TableResult<DOSProjectGroup> getProjectGroupByName(DOSProjectGroup projectGroup,DOSPageVo pageVo) {
        Assert.isTrue(ObjectUtil.isNotNull(projectGroup.getGroupName()),"项目组名称不能为空");
        Page<DOSProjectGroup> page = new Page<>(pageVo.getPageNum(),pageVo.getPageSize());
        TableResult<DOSProjectGroup> tableResult = new TableResult<>();
        LambdaQueryWrapper<DOSProjectGroup> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.like(DOSProjectGroup::getGroupName,projectGroup.getGroupName()).orderByDesc(DOSProjectGroup::getCreateTime);
        Page<DOSProjectGroup> groupPage = baseMapper.selectPage(page, queryWrapper);
        Pagination p = Pagination.builder().pageNum(groupPage.getCurrent()).pageSize(groupPage.getSize()).total(groupPage.getTotal()).build();
        tableResult.setPagination(p);
        tableResult.setList(groupPage.getRecords());

        return tableResult;
    }

    @Override
    public List<DOSProjectGroup> getListPage() {
        return this.list();
    }

    @Override
    public List<DOSProjectGroupPo> getCascade() {
        BaseUserVM user = (BaseUserVM) SecurityUtils.getSubject().getPrincipal();
        List<DOSProjectGroupPo> projectGroups;
        // 根据登录人员的角色信息查询项目组和项目列表
        if (user.getAdminRole()){
            projectGroups = baseMapper.getCascadeAdmin();
        } else {
            projectGroups = baseMapper.getCascadeByUserId(user.getId());
        }
        Map<Integer, List<DOSProjectGroupPo>> groupMap = projectGroups.stream().collect(Collectors.groupingBy(DOSProjectGroupPo::getGroupId));
        List<DOSProjectGroupPo> dosProjectGroupPos = new ArrayList<>();
        for (Map.Entry<Integer, List<DOSProjectGroupPo>> groupList : groupMap.entrySet()) {
            DOSProjectGroupPo dosProjectGroupPo = groupList.getValue().get(0);
            List<DOSProject> projects = new ArrayList<>();
            for (DOSProjectGroupPo projectPo : groupList.getValue()) {
                DOSProject project = DOSProject.builder()
                        .id(projectPo.getProjectId())
                        .projectName(projectPo.getProjectName())
                        .build();
                projects.add(project);
            }
            //按照projectId进行倒排序
            projects = projects.stream().sorted(Comparator.comparing(DOSProject::getId).reversed()).collect(Collectors.toList());
            dosProjectGroupPo.setProjects(projects);
            dosProjectGroupPos.add(dosProjectGroupPo);
        }
        //按照groupId进行倒排序
        return dosProjectGroupPos.stream().sorted(Comparator.comparing(DOSProjectGroupPo::getGroupId).reversed()).collect(Collectors.toList());
    }

    @Override
    public List<String> getSimilarProjectGroupName(String groupName,Double similarityLimit) {
        return baseMapper.getSimilarProjectGroupName(groupName,similarityLimit);
    }
}
